package top.xtcoder.xtpsd.core.layermask.handle.effect;

import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.nio.charset.Charset;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import top.xtcoder.xtpsd.core.layermask.handle.effect.base.dto.EffectObjTypeEnum;
import top.xtcoder.xtpsd.core.layermask.handle.effect.baseinterface.IEffectObjHandler;
import top.xtcoder.xtpsd.core.layermask.handle.effect.lang.EffectObjHandleChain;
import top.xtcoder.xtpsd.log.Log;
import top.xtcoder.xtpsd.utils.ByteUtil;

public class LayerEffectTyShHandler implements ILayerEffectHandler{
	private static final Log log = Log.getLog(LayerEffectTyShHandler.class);
	
	@Override
	public Map<String, Object> handle(byte[] effectData) throws IOException {
		try(InputStream inputStream = new ByteArrayInputStream(effectData)) {
			int version = ByteUtil.readByteToInt(inputStream, 2);
			
			double xx = ByteUtil.readByteToDouble8(inputStream);
			double xy = ByteUtil.readByteToDouble8(inputStream);
			double yx = ByteUtil.readByteToDouble8(inputStream);
			double yy = ByteUtil.readByteToDouble8(inputStream);
			double tx = ByteUtil.readByteToDouble8(inputStream);
			double ty = ByteUtil.readByteToDouble8(inputStream);
			
			int textVersion = ByteUtil.readByteToInt(inputStream, 2);
			int textDescriptorVersion = ByteUtil.readByteToInt(inputStream, 4);
			Map<String, Object> textData = parseData(inputStream);
			
			int warpVersion = ByteUtil.readByteToInt(inputStream, 2);
			int warpDescriptorVersion = ByteUtil.readByteToInt(inputStream, 4);
			Map<String, Object> warpData = parseData(inputStream);
			
			double left = ByteUtil.readByteToDouble8(inputStream);
			double top = ByteUtil.readByteToDouble8(inputStream);
			double right = ByteUtil.readByteToDouble8(inputStream);
			double bottom = ByteUtil.readByteToDouble8(inputStream);
			
			
			Map<String, Object> map = new HashMap<>();
			map.put("version", version);
			map.put("xx", xx);
			map.put("xy", xy);
			map.put("yx", yx);
			map.put("yy", yy);
			map.put("tx", tx);
			map.put("ty", ty);
			map.put("textVersion", textVersion);
			map.put("textDescriptorVersion", textDescriptorVersion);
			map.put("textData", textData);
			map.put("warpVersion", warpVersion);
			map.put("warpDescriptorVersion", warpDescriptorVersion);
			map.put("warpData", warpData);
			map.put("left", left);
			map.put("top", top);
			map.put("right", right);
			map.put("bottom", bottom);
			
			return map;
		}
	}
	
	private Map<String, Object> parseData(InputStream inputStream) throws IOException {
		Map<String, Object> data = new HashMap<>();
		
		String name = ByteUtil.readByteToUnicodeStr(inputStream);
		String classId = ByteUtil.readByteToClassId(inputStream);
		int count = ByteUtil.readByteToInt(inputStream, 4);
		List<Map<String, Object>> effectList = new ArrayList<Map<String, Object>>();
		for(int i = 0; i < count; i ++) {
			int keyLength = ByteUtil.readByteToInt(inputStream, 4);
			keyLength = keyLength < 4 ? 4 : keyLength;
			String key = ByteUtil.readByteToStr(inputStream, keyLength);
			String type = ByteUtil.readByteToStr(inputStream, 4);
			
			IEffectObjHandler hc = EffectObjHandleChain.get(type);
			if(hc != null) {
				Map<String, Object> propertie = hc.handle(inputStream);
				propertie.put("key", key);
				propertie.put("type", type);
				effectList.add(propertie);
			}else {
				log.log("parseTextData.key=%s, type=%s not found", key, type);
			}
		}
		data.put("name", name);
		data.put("classId", classId);
		data.put("effectList", effectList);
		return data;
	}
}
